#include "stdafx.h"
#include "Render.h"


Render::Render()
{
	m_vaoMesh = nullptr;
}

Render::~Render()
{
	DelMaterials();
}

void Render::DelMaterials()
{
	for (auto m : m_materials)
	{
		delete m;
	}
	m_materials.clear();
}

void Render::SetMaterial(int index, Material *mate)
{
	if (m_materials[index]) delete m_materials[index];
	m_materials[index] = mate;
}

void Render::SetMesh(VaoMesh *vaoMesh)
{
	DelMaterials();
	m_vaoMesh = vaoMesh;
	int count = m_vaoMesh->m_subMeshs.size();
	m_materials.resize(count);
}

void Render::SetMesh(VaoMesh *vaoMesh, std::vector<Material> &materials, Shader *shader)
{
	DelMaterials();
	m_vaoMesh = vaoMesh;
	int count = m_vaoMesh->m_subMeshs.size();
	m_materials.resize(count);
	auto dest = &m_materials[0];
	for (int i = 0; i < count; i++)
	{
		dest[i] = new Material(materials[i]);
		dest[i]->m_shader = shader;
	}
}

void Render::Draw(int instanceCount)
{
	glBindVertexArray(m_vaoMesh->GetVao());
	auto indicesType = m_vaoMesh->GetIndicesType();
	auto indicesEleSize = m_vaoMesh->GetIndicesElementSize();
	auto mate = &m_materials[0];
	int iMate = 0;

	for (auto &smesh : m_vaoMesh->m_subMeshs)
	{
		(*mate)->Use();
		mate++;
		if (instanceCount > 1)
		{
			if (indicesType) glDrawElementsInstanced(smesh.mode, smesh.vertElementCount, indicesType, (void*)(smesh.vertElementLocation * indicesEleSize), instanceCount);
			else glDrawArraysInstanced(smesh.mode, smesh.vertElementLocation, smesh.vertElementCount, instanceCount);
		}
		else
		{
			if (indicesType) glDrawElements(smesh.mode, smesh.vertElementCount, indicesType, (void*)(smesh.vertElementLocation * indicesEleSize));
			else glDrawArrays(smesh.mode, smesh.vertElementLocation, smesh.vertElementCount);
		}
	}
	glBindVertexArray(0);
	Shader::UseProgram0();
}

Material *Render::GetMaterial(int i)
{
	return m_materials[i];
}

int Render::GetMaterialCount()
{
	return m_materials.size();
}
